package com.sunbim.rsrv.service.impl;

import cn.hutool.core.util.ObjectUtil;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.sunbim.rsrv.common.exception.RequestException;
import com.sunbim.rsrv.mapper.RelicsMapper;
import com.sunbim.rsrv.mapper.RiskStatueMapper;
import com.sunbim.rsrv.pojo.RiskStatue;
import com.sunbim.rsrv.service.RiskStatueService;
import com.sunbim.rsrv.util.common.ProjectUtil;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.List;

@Slf4j
@Service
public class RiskStatueServiceImpl extends ServiceImpl<RiskStatueMapper, RiskStatue> implements RiskStatueService {
    @Autowired
    RelicsMapper relicsMapper;

    @Autowired
    RiskStatueMapper riskStatueMapper;

    @Override
    public RiskStatue selectByRelicsId(Integer userId, Integer relicsId) {
        QueryWrapper<RiskStatue> wrapper = new QueryWrapper<>();
        wrapper.eq("relics_id", relicsId);
        RiskStatue riskStatue = riskStatueMapper.selectOne(wrapper);
        if (ObjectUtil.isNull(riskStatue)) throw new RequestException("文物id: " + relicsId + " 的风险数据不存在");
        if(riskStatue.getBody() != null)
            riskStatue.getBody().setLevel(getLevel(userId, relicsId, riskStatue.getBody().getScore(),"body"));
        if(riskStatue.getAuxiliary() != null)
            riskStatue.getAuxiliary().setLevel(getLevel(userId, relicsId, riskStatue.getAuxiliary().getScore(),"auxiliary"));

        return riskStatue;
    }

    private int getLevel(Integer userId, Integer relicsId, Integer score, String column) {
        /* 计算风险等级 */
        int level;
        if (score == null || score == 0) level = 0;
        else {
            // 获取该文物在对应用户下的总分排名
            Integer rank = riskStatueMapper.getRank(userId, relicsId, column);
            // 根据文物的所属用户id 获取所有风险数据
            List<RiskStatue> list = getAllByUserId(userId);
            // 如果总数小于等于4, 获取前4名,去掉总分为0的数据, 排序取得风险等级
            if (list.size() <= 4) {
                // 统计总分不为0的风险数据
                int count = 0;
                for (RiskStatue riskStatue : list) {
                    if("body".equals(column)){
                        if (0 != riskStatue.getBody().getScore()) ++count;
                    } else if ("auxiliary".equals(column)) {
                        if (0 != riskStatue.getAuxiliary().getScore()) ++count;
                    }
                }
                // 若总分均不为0
                if (count == list.size()) level = count - rank + 1;
                    // 若存在总分为0
                else level = count - rank + 2;
            }
            // 否则根据排名和总数计算前百分位, 得到风险等级
            else level = ProjectUtil.countLevel(rank, list.size());
        }
        return level;
    }

    @Override
    public void updateByRiskId(RiskStatue params) {
        boolean isIdExist = riskStatueMapper.idExist(params.getId());
        if (!isIdExist) throw new RequestException("风险id: " + params.getId() + " 不存在");

        RiskStatue.Body body = params.getBody();
        body.setScore(body.getBuckling() + body.getContaminate() + body.getOther() + body.getWeathering());
        RiskStatue.Auxiliary auxiliary = params.getAuxiliary();
        auxiliary.setScore(auxiliary.getCracking() + auxiliary.getStructure());
        params.setTotalScore(body.getScore() + auxiliary.getScore());
        riskStatueMapper.updateById(params);
    }

    public List<RiskStatue> getAllByUserId(Integer userId) {
        QueryWrapper<RiskStatue> wrapper = new QueryWrapper<>();
        wrapper.eq("user_id", userId);
        return riskStatueMapper.selectList(wrapper);
    }
}
